package controleur;

import java.io.FileInputStream;
import java.sql.*;

public class ConnexionBD
{
    private static final String URL = "jdbc:mysql://98.143.215.172:8080/";
    private static final String DB_NAME = "bibliotheque";
    private static final String DRIVER = "com.mysql.jdbc.Driver";
    private static final String USER_NAME = "root";
    private static final String PASSWORD = "root";
    private Connection con = null;
    private PreparedStatement pstmt = null;
    private ResultSet results = null;

    /**
     * Crée une connexion à la BD
     * @throws SQLException 
     */
    private void create_connexion() throws SQLException
    {
        try {
            Class.forName(DRIVER);
        } catch (ClassNotFoundException e) {
            System.err.println("Error in create_connexion: " + e);
        }

        this.con = DriverManager.getConnection(URL + DB_NAME, USER_NAME, PASSWORD);
    }

    /**
     * Ferme la connexion à la BD
     */
    public void close()
    {
        try {
            this.con.close();
        } catch (SQLException e) {
            System.err.println("Error in close: " + e.getStackTrace());
        }
    }

    /**
     * Prépare un statement. Chaque `?` est transformer avec setString();
     * @param q La requête
     * @param param Les paramêtres de la requêtes
     * @throws SQLException 
     */
    private void prepare_statement(String q, String... param) throws SQLException
    {
        int i = 0;

        this.pstmt = this.con.prepareStatement(q);

        /* Remplies tous les '?' dans les requêtes */
        for (String p : param) {
            i++;
            this.pstmt.setString(i, p);
        }
    }

    /**
     * Execute une requête. Des `select` seulement.
     * @param q
     * @param param
     * @return 
     */
    public ResultSet execute_query(String q, String... param)
    {
        try {
            this.create_connexion();
            this.prepare_statement(q, param);
            this.results = this.pstmt.executeQuery();
        } catch (Exception e) {
            System.err.println("Error in execute_query: " + e);
        } 

        return this.results;
    }

    /**
     * Execute une requête. Autre qu'un select.
     * @param q
     * @param param
     * @return 
     */
    public int execute_update(String q, String... param)
    {
        int r = 0;

        try {
            this.create_connexion();
            this.prepare_statement(q, param);
            r = this.pstmt.executeUpdate();
        } catch (Exception e) {
            System.err.println("Error in execute_update:" + e);
        } 

        return r;
    }
    
    /**
     * Execute une requête pour une image.
     * @param q
     * @param fin
     * @param param
     * @return 
     */
    public ResultSet execute_blob_query(String q, FileInputStream fin, String... param)
    {
        int i = 1;

        try {
            this.create_connexion();
            this.prepare_statement(q);
            this.pstmt.setBlob(1, fin);

            /* Remplies tous les '?' dans les requêtes */
            for (String p : param) {
                i++;
                this.pstmt.setString(i, p);
            }
            
            this.results = this.pstmt.executeQuery();
        } catch (Exception e) {
            System.err.println("Error in execute_blob_query:" + e);
        } 
        
        return this.results;
    }

    /**
     * Cas spécial pour les blobs Le premier '?' dans la String va être utiliser
     * pour le FileInputStream
     */
    public int execute_blob_update(String q, FileInputStream fin, String... param)
    {
        int r = 0;
        int i = 1;

        try {
            this.create_connexion();
            this.prepare_statement(q);
            this.pstmt.setBlob(1, fin);

            /* Remplies tous les '?' dans les requêtes */
            for (String p : param) {
                i++;
                this.pstmt.setString(i, p);
            }
            
            r = this.pstmt.executeUpdate();
        } catch (Exception e) {
            System.err.println("Error in execute_blob_update:" + e);
        } 
        
        return r;
    }
}